Encontro 2 | 19/08/20024 Henrique Costa | Métodos Estratégicos em FinQuant
Dados e R
Funções
Receitas permitem que os chefs preparem guloseimas saborosas
As receitas pedem ingredientes
Recipes involve one or more steps
As etapas transformam os ingredientes em guloseimas
Funções são como receitas personalizáveis
Funções solicitam entradas (“argumentos”)
As funções envolvem uma ou mais linhas de código
O código transforma entradas em saídas
O uso de funções requer parênteses (geralmente)
doce <- f(ing1, ing2)
Funções - Prática
# CASO DE USO: A função pode executar uma tarefa de forma mais fácil e legível# MODELO: saída <- nome_da_função(entrada)9^ (1/2)x <-sqrt(9)x# ==============================================================================# LIÇÃO: Também podemos usar funções para transformar objetosy <-9sqrt(y)# ==============================================================================# LIÇÃO: Podemos até usar funções para transformar o resultado dos cálculos2/3round(2/3)# ==============================================================================# LIÇÃO: Podemos personalizar o que uma função faz usando argumentos# MODELO: saída <- nome_da_função(argumento, nome_do_argumento = valor_do_argumento)round(2/3, digits =2)round(2/3, digits =3)# ==============================================================================# LIÇÃO: Alguns argumentos são opcionais porque têm valores padrãoround(2/3) # the default value for digits is 0round(2/3, digits =0)
Vectores
Vetores combinam objetos semelhantes em uma coleção
Gosto de imaginar um trem puxando vários vagões
Um vetor é um objeto com muitos subobjetos
Nós nos referimos a cada subobjeto como um elemento
Algumas funções transformam cada elemento um de cada vez
Dobrar a quantidade de carga em cada vagão
Algumas funções resumir em todos os elementos
Calcule a carga total em todos os vagões do trem
v <- c(1, 2, 3, 4, 5)
Vetores - Prática
# LIÇÃO: Podemos combinar vários elementos em um vetor# MODELO: nome_do_vetor <- c(elemento1, elemento2, elemento3)x <-491625# errorx <-c(4, 9, 16, 25)xy <-c(2, 3)y# ==============================================================================# LIÇÃO: Também podemos combinar vários vetores e elementosc(x, y)c(x, y, 20)# ==============================================================================# CASO DE USO: Operadores matemáticos transformarão cada elemento individualmentex +1x *3x # mas, novamente, isso não será salvo a menos que você use atribuição# ==============================================================================# CASO DE USO: Algumas funções também transformarão cada elemento individualmentesqrt(x)log(x)# ==============================================================================# CASO DE USO: Outras funções resumirão o vetor com um único númerolength(x)sum(x)mean(x)
Strings
Ao programar com R, precisamos de uma maneira de distinguir
Nomes de objetos/funções (por exemplo, a função mean)
Dados de texto/caractere (por exemplo, a palavra mean)
Strings são a maneira do R armazenar dados de texto
Strings podem armazenar qualquer caractere (sem regras!)
As strings são criadas e exibidas com quotes
::::
Strings
R tem ótimas ferramentas para trabalhar com strings
As strings podem ser coletadas em vetores
Funções especiais podem transformar strings
name <- "John Doe"
:::
Strings - Prática
# CASO DE USO: Strings são a principal maneira de armazenar dados de caracteres em Rmy_color <- red # errormy_color <-"red"# correto# ==============================================================================# CASO DE USO: Strings também podem armazenar símbolos não permitidos em nomes de objetosdye <-"red#40"dyedyes <-c("red#40", "blue#02")dyes# ==============================================================================# ARMADILHA: Muitas operações que você pode fazer com números não funcionarão para stringsdyes +1# errormean(dyes) # error# ==============================================================================# CASO DE USO: Mas outras operações funcionam para ambos ou mesmo apenas para stringslength(dyes)nchar(dyes)dyes2 <-toupper(dyes)dyes2
Packages (Pacotes)
Livros de receitas são uma ótima maneira de aprender a cozinhar
Eles contêm muitas receitas e instruções
Navegue em uma livraria online para encontrar um livro de receitas
Encomende para adicionar à sua estante pessoal
Para usar, retire o livro de receitas da prateleira
Packages (Pacotes)
Pacotes são como livros de receitas para R
Eles contêm funções e conjuntos de dados úteis
Navegue em um repositório online para um pacote
Instale para adicioná-lo à sua biblioteca pessoal
Para usar, carregue o pacote da biblioteca
library("pkg_name")
Packages - Prática
# CASO DE USO: O pacote stringr adiciona uma função para corrigir a capitalizaçãostudents <-c("mary anne", "BENjamin", "Lee")# ==============================================================================# ARMADILHA: Mas não podemos usar essa função sem instalar o pacotestr_to_title(students) # error# ==============================================================================# LIÇÃO: Instalando um pacote usando RStudio# - RStudio > Extras pane > Packages tab > Install button# ==============================================================================# ARMADILHA: Também precisamos carregar o pacote antes de podermos usá-lostr_to_title(students) # error# ==============================================================================# LIÇÃO: Carregamos o pacote usando library()library("stringr")str_to_title(students) # pronto isso funciona!# ==============================================================================# LIÇÃO: Também podemos manter nossos pacotes atualizados usando o RStudio# RStudio > Extras pane > Packages tab > Update button
Wrangle I
Princípio de Dados Tidy (Arrumados)
Existem muitas maneiras de armazenar dados
Aprenderemos o formato tidy data
Os dados devem ser retangulares
Cada variável tem sua própria coluna
Cada observação tem sua própria linha
Cada valor tem sua própria célula
Outros conselhos sobre dados
Nomeie todas as variáveis na primeira linha
Isso é chamado de linha de cabeçalho
Evite células mescladas para armazenamento de dados
Estes são bons para comunicação
Evite células vazias sempre que possível
Marcar dados ausentes como NA
Evite formatação como dados para armazenamento
por exemplo, codificação de cores não redundante
Arrumando (Tidying) exemplo 1
Não Arrumado (Tidy)
Nome
Ann
Bob
Cat
Dom
Idade
13
10
11
11
Peso
56.4
46.8
41.3
43.3
❌ Aqui, cada linha é uma variável e cada coluna é uma observação.
Arrumado (Tidy)
Nome
Idade
Peso
Ann
13
56.4
Bob
10
46.8
Cat
11
41.3
Dom
11
43.3
✔️ Aqui, cada coluna é uma variável e cada linha é uma observação.
Arrumando (Tidying) exemplo 2
Não arrumado (Tidy)
Nome:
Ann
Bob
Cat
Dom
Idade
Peso
13
56.4
10
46.8
11
41.3
11
43.3
❌ Aqui, temos dados que não são retangulares porque a variável Names tem sua própria linha.
Arrumado (Tidy)
Nome
Idade
Peso
Ann
13
56.4
Bob
10
46.8
Cat
11
41.3
Dom
11
43.3
✔️ Aqui, tornamos os dados retangulares movendo a variável Nomes para sua própria coluna.
Arrumando (Tidying) exemplo 3
Não arrumado (Tidy)
country
year
cases / population
Afghanistan
1999
NA / 19987071
2000
2666 / 20595360
Brazil
1999
37737 / 172006362
2000
80488 / 174504898
China
1999
212258 / 1272915272
2000
213766 / 1280428583
❌ Aqui, mesclamos células e dois valores armazenados em uma única célula.
Arrumado (Tidy)
country
year
cases
population
Afghanistan
1999
NA
19987071
Afghanistan
2000
2666
20595360
Brazil
1999
37737
172006362
Brazil
2000
80488
174504898
China
1999
212258
1272915272
China
2000
213766
1280428583
✔️Aqui, desfazemos a mesclagem dos países e separamos as variáveis de casos e populações em colunas.
Arrumando (Tidying) exemplo 4
Não arrumado
student
grade
Amber
91.5
A-
Bristol
86.2
B
Charlene
94.0
A
Diego
89.3
B+
Legend: Psych. Major, Psych. Minor
❌ Aqui, temos um nome de variável ausente e formatação como dados.
Arrumado
student
psych
grade
letter
Amber
major
91.5
A-
Bristol
minor
86.2
B
Charlene
major
94.0
A
Diego
NA
89.3
B+
✔️ Aqui, adicionamos uma coluna para a variável psych, removemos a legenda e nomeamos a variável letter.
Arrumando (Tidying) exemplo 5
Não arrumado
student
grade
letter
Amber
91.5
A-
Bristol*
94.2
A
Class Summary
As
2
Yay!
Bs
0
*Grade was revised.
❌ Aqui, temos dois tipos de dados em um arquivo e uma nota de rodapé como dados.
Arrumado
student
grade
letter
revised
Amber
91.5
A-
FALSE
Bristol
94.2
A
TRUE
letter
count
notes
A
2
Yay!
B
0
✔️ Aqui, dividimos os dados em duas tabelas separadas e adicionamos as variáveis revisadas e notas.
Tabelas (Tibbles)
R funciona particularmente bem com dados organizados
Armazenamos dados organizados em data frames ou tibbles
Tibbles são apenas tabelas mais sofisticadas (ou seja, eles têm alguns recursos extras)
Para usar tibbles, precisamos do pacote tidyverse
Tibbles são construídos a partir de um ou mais vetores
Os vetores devem ter o mesmo comprimento
Eles podem conter diferentes tipos de dados
Vetores
Começamos com três objetos vetoriais separados que têm todos o mesmo comprimento.
Nós configuramos para que o \(n\)-ésimo vagão em cada trem corresponda à mesma observação.
Tibble
Então combinamos os vetores em um único objeto tibble (ou data frame).
Agora, conforme o tibble se move, as variáveis sempre ficam juntas.
Tibbles - Prática
# CONFIGURAÇÃO: Instale e carregue o pacote tidyverse# Extras pane > Packages tab > Installlibrary(tidyverse)# ==============================================================================# LIÇÃO: Crie um tibble a partir de vetoresx <-c(10, 20, 30, 40)xy <- x *2-4ymy_tibble <-tibble(x, y)my_tibble# ==============================================================================# CASO DE USO: Você pode misturar diferentes tipos de vetores em um único tibblefirst_names <-c("Adam", "Billy", "Caitlyn", "Debra")age_years <-c(12, 13, 10, NA)guests <-tibble(first_names, age_years)guests# ==============================================================================# DICA: Para economizar tempo, você também pode criar os vetores na chamada tibblegradebook <-tibble(grade =c(95, 83, 90, 76),letter =c("a", "b", "a-", "c"))gradebook# ==============================================================================# ARMADILHA: Não tente combinar tibbles com comprimentos diferentesy <-c(1, 2, 3)x <-c("a", "b")tibble(y, x) #error# ==============================================================================# LIÇÃO: No entanto, a exceção é que R irá "reciclar" um único valortibble(y, x ="a")# ==============================================================================# LIÇÃO: Você pode "extrair" um vetor de um tibble usando $mytibble <-tibble(x =c(1, 2, 3, 4, 5), y ="test")mytibble$xmytibble$y# ==============================================================================# ARMADILHA: Não tente extrair um vetor que não existemytibble$z #error
Tabelas longas e largas (long x wide)
Tabelas longas e largas (long x wide)
Importação e Exportação
Os dados geralmente são armazenados em arquivos de dados
Importar arquivos para R é chamado reading
Exportar arquivos de R é chamado writing
Um tipo de arquivo de dados conveniente é um CSV
Isto significa valores separados por vírgula
Um arquivo CSV é fácil de compartilhar com outras pessoas
O pacote tidyverse pode ler/escrever CSVs
Outros pacotes podem ler/escrever outros tipos (e.g., readxl, haven, rio, googlesheets4)
Read/Write - Prática
# CONFIGURAÇÃO: Carregue o pacote tidyverse (se ainda não o fez)library(tidyverse)# ==============================================================================# CASO DE USO: Crie um tibble e grave-o em um arquivogradebook <-tibble(id =c(123, 456, 789),grade =c("A", "B", "A"))gradebookwrite_csv(gradebook, file ="gradebook.csv")# NOTA: Você pode ver o novo arquivo no painel Extras > aba Arquivos.# Você pode abrir o arquivo em outro programa (por exemplo, Microsoft Excel).# Você também pode enviar este arquivo por e-mail para outra pessoa para compartilhá-lo.# ==============================================================================# ARMADILHA: Não troque a ordem do tibble e do filewrite_csv("gradebook.csv", gradebook) # error# ==============================================================================# CASO DE USO: Ler em um arquivo contendo dadosold_gradebook <-read_csv("gradebook.csv")old_gradebook# NOTA: read_csv() examinará e adivinhará o tipo de dado de cada variável.# Você pode dizer a ele o tipo de dado de cada variável, mas isso é mais avançado.# ==============================================================================# ARMADILHA: Não use as funções read.csv() e write.csv()old_gradebook <-read.csv("gradebook.csv") # not a tibbleold_gradebook
Wrangle II
Vérbos basicos em data wrangling
tidyverse fornece ferramentas para controlar tibbles
Essas funções são nomeadas após verbos
Então, se você nomear seus objetos com base em substantivos…
…seu código se torna mais fácil de ler
Substantivo(substantivo) ❌
Verbo(substantivo) ✔️
blender(fruit)
blend(fruit)
screwdriver(screw)
drive(screw)
boxcutter(box)
cut(box)
Verbos focados em colunas
Selecionar retém apenas certas colunas/variáveis
select(TBL, VAR_KEEP, -VAR_DROP)
Mutate adiciona ou transforma colunas/variáveis
mutate(TBL, NEW_VAR = OLD_VAR / 1000)
Rename altera os nomes das colunas/variáveis
rename(TBL, NEW_NAME = OLD_NAME)
Relocate altera a ordem das colunas/variáveis
relocate(TBL, VAR_MOVE, .after = OTHER_VAR)
Select - Prática
# CONFIGURAÇÃO: Carregar pacote e inspecionar exemplo tibblelibrary(tidyverse) # inclui o pacote dplyrstarwars# ==============================================================================# CASO DE USO: Reter apenas as variáveis especificadassw <-select(starwars, name)swsw <-select(starwars, name, sex, species)sw# ==============================================================================# ARMADILHA: Não esqueça de salvar a alteração com a atribuiçãoselect(starwars, name, sex, species)starwars # ainda inclui todas as variáveis# ==============================================================================# CASO DE USO: Reter todas as variáveis entre duas variáveissw <-select(starwars, name, hair_color:eye_color)sw# ==============================================================================# CASO DE USO: Reter todas as variáveis, exceto as especificadassw <-select(starwars, -sex, -species)swsw <-select(starwars, -c(sex, species))swsw <-select(starwars, -c(hair_color:starships))sw
Mutate - Prática
# CONFIGURAÇÃO: Criar exemplo tibblepatients <-tibble(id =c("S1", "S2", "S3"),feet =c(6, 5, 5),inches =c(1, 7, 2),pounds =c(176.3, 124.9, 162.6))patients# ==============================================================================# CASO DE USO: Adicionar uma ou mais variáveisp2 <-mutate(patients, sex =c("M", "F", "F"))p2ages <-c(32, 41, 29)p2 <-mutate(patients, ages = ages)p2p2 <-mutate( patients, sex =c("M", "F", "F"), ages = ages)p2# ==============================================================================# CASO DE USO: Calcular variáveisp2 <-mutate(patients, height = feet + inches /12)p2p2 <-mutate(patients, ln_pounds =log(pounds))p2# ==============================================================================# CASO DE USO: Substituir variáveispatients <-mutate(patients, height = height /3.281)patients# ==============================================================================# CASO DE USO: Variáveis duplicadasp2 <-mutate(patients, weight = pounds)p2 # tanto peso quanto libras existem
Rename / Relocate - Prática
# CASO DE USO: Alterar o nome de uma ou mais variáveisstarwarssw <-rename(starwars, Character = name)swsw <-rename(starwars, height_cm = height, mass_kg = mass)sw# ==============================================================================# ARMADILHA: Não troque a ordem e tente old_name = new_namesw <-rename(starwars, name = Character) # error# ==============================================================================# CASO DE USO: Mover variáveis antes ou depois de outra variávelstarwarssw <-relocate(starwars, species, sex, .before = height)swsw <-relocate(starwars, species, sex, .after = name)sw# ==============================================================================# ARMADILHA: Não se esqueça do ponto final!sw <-relocate(starwars, sex, before = height) sw # altura foi renomeada acidentalmente para antes
Verbos focados em linha
Arrange classifica as linhas com base em seus valores
arrange(TBL, VAR_SORT_UP)
arrange(TBL, desc(VAR_SORT_DOWN))
arrange(TBL, VAR_SORT_1ST, VAR_SORT_2ND)
Filter retém certas linhas com base em critérios
filter(TBL, DBL_CRIT > 0)
filter(TBL, STR_CRIT == "A")
filter(TBL, CRIT1, CRIT2)
Arrange - Prática
# CASO DE USO: Classificar observações por uma variávelstarwarssw <-arrange(starwars, height)sw # classificado por altura, crescentesw <-arrange(starwars, name)sw # classificado por nome, em ordem alfabética# ==============================================================================# CASO DE USO: Classificar observações por uma variável, em ordem reversasw <-arrange(starwars, desc(height))sw # classificado por altura, decrescentesw <-arrange(starwars, desc(name))sw # classificado por nome, em ordem alfabética reversa# ==============================================================================# CASO DE USO: Classificar observações por múltiplas variáveissw <-arrange(starwars, hair_color, mass)sw # classificado por cor do cabelo, então os empates são quebrados por massa
Filter - Prática
# CASO DE USO: Reter apenas observações que atendem a um critériosw <-filter(starwars, mass >100)sw # apenas observações com massa maior que 100sw <-filter(starwars, mass <=100)sw # apenas observações com massa menor ou igual a 100sw <-filter(starwars, species =="Human")sw # apenas observações com espécies iguais ao Humanosw <-filter(starwars, species !="Human")sw # apenas observações com espécies diferentes do Humano# ==============================================================================# ARMADILHA: Não tente usar um único = para testar igualdadesw <-filter(starwars, height =150) # errorsw <-filter(starwars, height ==150) # correctsw # ==============================================================================# ARMADILHA: Não se esqueça de que R diferencia maiúsculas de minúsculassw <-filter(starwars, species =="human")sw # nenhuma observação restante (porque deveria ser Humano)# ==============================================================================# CASO DE USO: Reter apenas observações que atendem a critérios complexossw <-filter(starwars, mass >100& height >200)sw # apenas observações com massa acima de 100 E altura acima de 200sw <-filter(starwars, height <100| hair_color =="none")sw # somente observações com altura menor que 100 OU hair_color igual a nenhum# ==============================================================================# ARMADILHA: Não se esqueça de preencher as duas condiçõessw <-filter(starwars, mass >100&<200) # errorsw <-filter(starwars, mass >100& mass <200) # corretosw# ==============================================================================# ARMADILHA: Não tente igualar uma string a um vetorsw <-filter(starwars, species ==c("Human", "Droid")) # errorsw <-filter(starwars, species %in%c("Human", "Droid")) # correctsw
Filter Cheatsheet
Symbol
Description
Numérico
Charactere
<
Menor que
Sim
Não
<=
Menor ou igual á
Sim
Não
>
Maior que
Sim
Não
>=
Maior ou igual á
Sim
Não
==
Igual á
Sim
Sim
!=
diferente de
Sim
Sim
%in%
Encontre em
Sim
Sim
&
Lógico - “E”
Sim
Sim
|
Lógico - “Ou”
Sim
Sim
Wrangle III
Pipes & Pipelines
Como podemos fazer operações múltiplas em um objeto?
x <- 10
x2 <- sqrt(x)
x3 <- round(x2)
Isso funciona, mas é incômodo e propenso a erros
Uma abordagem melhor é usar pipes e pipelines
x3 <- 10 %>% sqrt() %>% round()
Gosto de ler %>% (ou |>) como “e então…”
“Pegue 10 e então sqrt() e então round()”
Pipes - Prática
# CONFIGURAÇÃO: Habilitar o atalho do operador de pipe# Tools > Global Options... > Code tab > Check "Use Native Pipe Operator"# Digite |> ou pressione Ctrl+Shift+M (Windows) / Cmd+Shift+M (Mac)# ==============================================================================# LIÇÃO: O pipe envia objetos para uma função como seu primeiro argumento# MODELO: x |> function_name() é o mesmo que function_name(x)x <-10y <-sqrt(x)yy <- x |>sqrt()y# ==============================================================================# ARMADILHA: Não se esqueça de remover o objeto da chamada de funçãox |>sqrt(x) # wrongx |>sqrt() # correto# ==============================================================================# CASO DE USO: Você ainda pode usar argumentos ao canalizarz <-round(3.14, digits =1)zz <-3.14|>round(digits =1)z# ==============================================================================# USECASE: Pipes são úteis com tibbles e funções para data wranglingstarwarssw <-select(starwars, name, species, height)swsw <- starwars |>select(name, species, height)sw# ==============================================================================# ARMADILHA: Não adicione um pipe sem um passo depois delesw <- starwars |>select(name, species, height) |># error
Pipelines - Prática
# CASO DE USO: Você pode encadear vários pipes para criar um pipelinex <-10|>sqrt() |>round()x# ==============================================================================# DICA: Se você quiser ver a saída de um pipeline, você pode canalizar para print()x <-10|>sqrt() |>round() |>print()# ==============================================================================# DICA: Para tornar seus pipelines mais legíveis, mova cada etapa para uma nova linhax <-10|>sqrt() |>round() |>print()# ==============================================================================# ARMADILHA: Não coloque o pipe no início de uma linhax <-10|>sqrt()|>round()|>print() # error# ==============================================================================# CASO DE USO: Encadeie uma série de verbos para controlar dados de forma flexíveltallones <- starwars |>select(name, species, height) |>rename(height_cm = height) |>mutate(height_ft = height_cm /30.48) |>filter(height_ft >7) |>arrange(desc(height_ft)) |>print()
Factors
Factors são usados para representar dados categóricos
Os fatores têm múltiplos [níveis] possíveis{.b .blue}
Os níveis são discretos e mutuamente exclusivos
Às vezes, as categorias são não ordenadas (nominais)
Ação ou Comédia ou Drama
Ásia ou Europa ou América do Norte
Às vezes, as categorias são ordenadas (ordinal)
Suave < Médio < Picante
XS < S < M < L < XL
Factors - Prática
# CASO DE USO: Peça a 10 crianças para pedirem 1: nuggets, 2: pizza ou 3: saladafood <-c(2, 2, 1, 2, 1, 2, 1, 1, 2, 2)food# ==============================================================================# LIÇÃO: Podemos transformar esse vetor em um fator com a função factor()food2 <-factor(food, levels =c(1, 2, 3))food2food3 <-factor(food, levels =c(1, 2, 3),labels =c("nuggets", "pizza", "salad"))food3# ==============================================================================# CASO DE USO: Também podemos contar cada nível de forma rápida e fácil com a função table()table(food3)# ==============================================================================# ARMADILHA: Não confunda níveis e rótulos (level/label)food4 <-factor(food, labels =c(1, 2, 3),levels =c("nuggets", "pizza", "salad"))food4 # cheio de <NA> porque não consegue encontrar esses níveis# ==============================================================================# CASO DE USO: Você também pode simplesmente inserir strings diretamente (como auto-rótulos)genre <-c("pop", "metal", "pop", "rock", "rap", "rap", "pop", "rock")genregenre2 <-factor(genre) # os níveis observados serão atribuídos em ordem alfabéticagenre2table(genre2)# ==============================================================================# LIÇÃO: Se ordinal, insira os níveis de baixo para alto e adicione ordenado = VERDADEIROsalsa <-c("hot", "mild", "medium", "mild", "medium", "medium")salsa2 <-factor(salsa, levels =c("mild", "medium", "hot"), ordered =TRUE)salsa2 # NOTA: Podemos querer visualizar ou modelar fatores ordinais de forma diferente# ==============================================================================# CASO DE USO: Trabalhando com fatores em um tibblecereal <-read_csv("cereal.csv")cerealcereal2 <-mutate(cereal, mfr =factor(mfr), type =factor(type))cereal2table(cereal2$mfr)table(cereal2$type)
Valores ausentes
Às vezes, seus dados terão valores ausentes
Talvez estes nunca tenham sido coletados
Talvez os valores tenham sido perdidos/corrompidos
Talvez o participante não respondeu
Precisamos dizer a R quais valores estão faltando
Para fazer isso, definimos esses valores como NA
As funções do tidyverse tornam isso fácil
A ausência é frequentemente “contagiosa” em R por exemplo, um vetor com NA tem uma média desconhecida
Valores ausentes - Prática
# CONFIGURAÇÃO: Precisaremos do tidyverse para as funções de leitura e mutaçãolibrary(tidyverse)# ==============================================================================# ARMADILHA: Códigos numéricos para ausências irão atrapalhar os cálculos em Rheights <-c(149, 158, -999) # aqui usamos -999 para representar um valor ausenterange(heights)mean(heights)log(heights) # nosso valor ausente não é mais -999# ==============================================================================# CASO DE USO: Use NA para ausência em vez dissoheights2 <-c(149, 158, NA)heights2log(heights2) # a NA continuou sendo NA (devido à contagiosidade)# ==============================================================================# LIÇÃO: Use na.rm = TRUE para fazer uma função de resumo ignorando os NAsmean(heights2) # a média é um NA (devido à contagiosidade)mean(heights2, na.rm =TRUE)range(heights2, na.rm =TRUE)# ==============================================================================# CASO DE USO: Lidando com valores ausentes em tibblescereal <-read_csv("cereal.csv")cereal$ratingrange(cereal$rating)# ==============================================================================# LIÇÃO: Use na_if() para converter valores específicos para NA durante a modificaçãocereal2 <- cereal %>%mutate(rating =na_if(rating, -999))cereal2$ratingrange(cereal2$rating, na.rm =TRUE)# ==============================================================================# LIÇÃO: Use read_csv(na) para converter valores específicos para NA durante a leituracereal3 <-read_csv("cereal.csv", na ="-999")cereal3$ratingrange(cereal3$rating, na.rm =TRUE)
Wrangle IV
Summarize
Embora armazenemos dados sobre muitas observações…
…frequentemente queremos resumir observações
Isto é como dobrar o tibble para uma linha
Vimos funções que resumem vetores
length(), sum(), min(), max()
mean(), median(), sd(), var()
summarize() nos permite usá-los em tibbles
Funciona de forma muito semelhante a mutate()
Ele sempre cria um tibble como saída
Summarize - Prática
# CONFIGURAÇÃO: Precisaremos do tidyverse e de um conjunto de dados de exemplolibrary(tidyverse)sales <-tibble(customer =c(1, 2, 3, 1, 3),store =c("A", "A", "A", "B", "B"),items =c(25, 20, 16, 10, 5),spent =c(685, 590, 392, 185, 123) ) |>print()# ==============================================================================# CASO DE USO: Resuma as vendas típicasmy_summary <- sales |>summarize(avg_items =mean(items),avg_spent =mean(spent) ) |>print()# ==============================================================================# ARMADILHA: Não use summary() em vez de summarise()my_summary <- sales |>summary(avg_items =mean(items),avg_spent =mean(spent) ) |>print() # não é um tibble# ==============================================================================# CASO DE USO: Use mais de uma função de resumomy_summary <- sales |>summarize(total_items =sum(items),total_spent =sum(spent),avg_items =mean(items),avg_spent =mean(spent) ) |>print()# ==============================================================================# CASO DE USO: Usar funções de contagemmy_counts <- sales |>summarize(n_sales =n(),n_customers =n_distinct(customer),n_stores =n_distinct(store) ) |>print()
Group Summarize
Também podemos resumir um tibble por grupo
Isto é como dobrar o tibble várias vezes
Especificamente, dobramos para uma linha por grupo
A sintaxe para resumir é idêntica
A única diferença é o tibble
Primeiro passamos por group_by()
Os pipelines tornam isso muito fácil
Group Summarize - Prática
# CONFIGURAÇÃO: Precisaremos do tidyverse e de um conjunto de dados de exemplolibrary(tidyverse)sales <-tibble(customer =c(1, 2, 3, 1, 3),store =c("A", "A", "A", "B", "B"),items =c(25, 20, 16, 10, 5),spent =c(685, 590, 392, 185, 123) ) |>print()# ==============================================================================# LIÇÃO: Passamos um tibble por group_by para agrupá-losalessales |>group_by(store) # observe que o display diz "agrupado"# ==============================================================================# CASO DE USO: Podemos então resumir e obter estatísticas por gruposales |>group_by(store) |>summarize(customers =n_distinct(customer),items_sold =sum(items),total_sales =sum(spent),avg_items =mean(items),avg_spent =mean(spent) )# ==============================================================================# CONFIGURAÇÃO: Vamos obter um conjunto de dados maior e mais realista# Extra pane > Packages tab > Install > nycflights13library("nycflights13")flights# ==============================================================================# CASO DE USO: Encontre a transportadora com os menores atrasos médiosflights |>group_by(carrier) |>summarize(m_delay =mean(dep_delay, na.rm =TRUE)) |>arrange(m_delay)# ==============================================================================# LIÇÃO: Também podemos agrupar por múltiplas variáveis# CASO DE USO: Vamos encontrar o dia do ano com mais voosflights |>group_by(month, day) |>summarize(n_flights =n()) |>arrange(desc(n_flights))
DataViz I
O que é um gráfico?
Uma visualização de dados que expressa os dados por meio de estética visual.
Por que expressamos dados em um gráfico?
Porque é importante visualizar dados antes de aplicar testes estatísticos inferenciais e descritivas.
Quarteto de Anscombe
Anscombe, F. J. (1973). Graphs in statistical analysis. The American Statistician, 27(1), 17–21.
Quarteto de Anscombe
Quarteto de Anscombe
x1
x2
x3
x4
y1
y2
y3
y4
1
10
10
10
8
8.04
9.14
7.46
6.58
2
8
8
8
8
6.95
8.14
6.77
5.76
3
13
13
13
8
7.58
8.74
12.74
7.71
4
9
9
9
8
8.81
8.77
7.11
8.84
5
11
11
11
8
8.33
9.26
7.81
8.47
6
14
14
14
8
9.96
8.10
8.84
7.04
7
6
6
6
8
7.24
6.13
6.08
5.25
8
4
4
4
19
4.26
3.10
5.39
12.50
9
12
12
12
8
10.84
9.13
8.15
5.56
10
7
7
7
8
4.82
7.26
6.42
7.91
11
5
5
5
8
5.68
4.74
5.73
6.89
Estatísticas Descritivas do Quarteto de Anscombe
Agrupadas por Conjunto
Características
1 N = 11
2 N = 11
3 N = 11
4 N = 11
x
Média
9.00
9.00
9.00
9.00
Desvio Padrão
3.32
3.32
3.32
3.32
y
Média
7.50
7.50
7.50
7.50
Desvio Padrão
2.03
2.03
2.03
2.03
Quarteto de Anscombe
Correlações do Quarteto de Anscombe
conjunto
correlação
1
0.8164205
2
0.8162365
3
0.8162867
4
0.8165214
Observação: Correlação calculada conforme a correlação de Pearson
Quarteto de Anscombe
Modelo de Regressão Linear do Quarteto de Anscombe
Fórmula: y ~ x
Conjunto
estimate
std.error
p.value.x
conf.low
conf.high
r.squared
adj.r.squared
1
0.5000909
0.1179055
0.002169629
0.2333701
0.7668117
0.6665425
0.6294916
2
0.5000000
0.1179637
0.002178816
0.2331475
0.7668525
0.6662420
0.6291578
3
0.4997273
0.1178777
0.002176305
0.2330695
0.7663851
0.6663240
0.6292489
4
0.4999091
0.1178189
0.002164602
0.2333841
0.7664341
0.6667073
0.6296747
Aplicando uma regressão linear teremos os mesmo \(p\)-valores, coeficientes, \(R^2\) e \(R^2\) ajustado para todos os quatro conjuntos.
The Datasaurus Dozen
O Datasaurus original foi criado por Alberto Cairo. As outras Dúzias é descrito no artigo “Same Stats, Different Graphs: Generating Datasets with VariedAppearance and Identical Statistics through Simulated Recoaling” de Justin Matejka e George Fitzmaurice.
The Datasaurus Dozen
Estatísticas Descritivas do Datasaurus Dozen
Agrupadas por Conjunto
Conjunto
Média(X)
Média(Y)
Desv. Pad(X)
Desv. Pad(Y)
Correlação(X e Y)
away
54.26610
47.83472
16.76982
26.93974
-0.06412835
bullseye
54.26873
47.83082
16.76924
26.93573
-0.06858639
circle
54.26732
47.83772
16.76001
26.93004
-0.06834336
dino
54.26327
47.83225
16.76514
26.93540
-0.06447185
dots
54.26030
47.83983
16.76774
26.93019
-0.06034144
h_lines
54.26144
47.83025
16.76590
26.93988
-0.06171484
high_lines
54.26881
47.83545
16.76670
26.94000
-0.06850422
slant_down
54.26785
47.83590
16.76676
26.93610
-0.06897974
slant_up
54.26588
47.83150
16.76885
26.93861
-0.06860921
star
54.26734
47.83955
16.76896
26.93027
-0.06296110
v_lines
54.26993
47.83699
16.76996
26.93768
-0.06944557
wide_lines
54.26692
47.83160
16.77000
26.93790
-0.06657523
x_shape
54.26015
47.83972
16.76996
26.93000
-0.06558334
The Datasaurus Dozen
Porque usar gráficos
O quarteto de Anscombe e o Datasaurus Dozen são maneiras de ilustrar a importância de visualizações na análise de dados. Deve-se sempre olhar um conjunto de dados graficamente antes de começar qualquer análise, pois estes exemplos, ilustram contextos nos quais as propriedades estatísticas básicas para descrever conjuntos de dados são inadequadas, ou insuficiêntes.
Descrevendo gráficos
Alguns gráficos simples são fáceis de descrever e podem até ter nomes prontos.
Descrevendo gráficos
Uma gramática de gráficos nos ajudará a descrever gráficos mais complexidade.
The Grammar of Graphics
A gramática dos gráficos é um conjunto de regras para descrever e criar visualizações de dados
Para tornar nossos dados visuais (e, portanto, colocar nossos lobos occipitais altamente evoluídos para funcionar)…
Conectamos variáveis a qualidades visuais
Representamos observações como objetos visuais
Isso requer alguns elementos fundamentais
Primeiro aprenderemos sobre eles na aula
Em seguida, aplicaremos em R usando {ggplot2}
Aesthetic Mappings
Os gráficos exigem mapeamentos estéticos, que conectam variáveis a qualidades visuais.
Scales
Os gráficos requerem escalas, que conectam valores a estética.
Geoms
Os gráficos requerem objetos geométricos (geoms), que representam as observações.
O básico de ggplot2
O pacote ggplot2 faz parte do tidyverse
Não há necessidade de instalar ou carregar separadamente
Trabalha bem com tibbles & data wrangling
Ele implementa a gramática dos gráficos em R
O “gg” significa “gramática de gráficos”
Assim, precisaremos fornecer os elementos fundamentais
Criaremos um pseudo-pipeline de comandos
Entretanto, usaremos + em vez de %>%
Isso é porque o {ggplot2} é anterior ao pipe do R
ggplot2 - Prática
# CONFIGURAÇÃO: Precisaremos do tidyverse e de um conjunto de dados de exemplolibrary(tidyverse)mpg# ==============================================================================# LIÇÃO: Primeiro, defina os dados para um tibblep <-ggplot(data = mpg)p# ==============================================================================# LIÇÃO: Em seguida, defina os mapeamentos estéticos com a função aes()p <-ggplot(data = mpg, mapping =aes(x = displ, y = hwy))p# ==============================================================================# DICA: Você pode usar aes() diretamente sem o argumento mappingp <-ggplot(mpg, aes(x = displ, y = hwy))p# ==============================================================================# LIÇÃO: Em seguida, defina as escalas posicionaisp <-ggplot(mpg, aes(x = displ, y = hwy)) +scale_x_continuous(name ="Engine Size (in liters)", limits =c(1, 7), breaks =1:7 ) +scale_y_continuous(name ="Highway Fuel Efficiency (in miles/gallon)",limits =c(10, 50),breaks =c(10, 20, 30, 40, 50) )p# ==============================================================================# LIÇÃO: Por fim, adicione um ponto geométrico (geom)p <-ggplot(mpg, aes(x = displ, y = hwy)) +scale_x_continuous(name ="Engine Size (in liters)", limits =c(1, 7), breaks =1:7 ) +scale_y_continuous(name ="Highway Fuel Efficiency (in miles/gallon)",limits =c(10, 50),breaks =c(10, 20, 30, 40, 50) ) +geom_point()# ==============================================================================# DICA: Se você deixar de fora as escalas, o R tentará adivinharp <-ggplot(mpg, aes(x = displ, y = hwy)) +geom_point()p# ==============================================================================# LIÇÃO: Também podemos personalizar o geom com argumentosp <-ggplot(mpg, aes(x = displ, y = hwy)) +geom_point(color ="red", shape ="square", size =2)p
O básico sobre Camadas
ggplot2 usa uma gramática em camadas de gráficos
Permite empilhar geoms (formas geométricas)
Camadas adiciona muitas possibilidades
Podemos transmitir ideias mais complexas
Podemos aprender mais sobre nossos dados
Mas ainda podemos descrever esses gráficos
Apenas descreva cada camada por vez
E descreva a ordenação das camadas
Camadas ggplot2 - Prática
# CONFIGURAÇÃO: Precisaremos do tidyverse e de um conjunto de dados de exemplolibrary(tidyverse)mpg# ==============================================================================# CASO DE USO: Adicionar uma geometria suave (geom_smooth), ou seja, linha de melhor ajuste. ggplot(mpg, aes(x = displ, y = hwy)) +geom_point() +geom_smooth()ggplot(mpg, aes(x = displ, y = hwy)) +geom_point() +geom_smooth(method ="lm")# ==============================================================================# CASO DE USO: Adicionar uma linha geom (ou seja, pontos de conexão)economicsggplot(economics, aes(x = date, y = unemploy)) +geom_point()ggplot(economics, aes(x = date, y = unemploy)) +geom_point() +geom_line(color ="orange", size =1)ggplot(economics, aes(x = date, y = unemploy)) +geom_line(color ="orange", size =1) +geom_point()# ==============================================================================# CASO DE USO: Adicionar linhas de referência geométricasggplot(economics, aes(x = date, y = unemploy)) +geom_hline(yintercept =0, color ="orange", size =1) +geom_line(color ="blue", size =1) +geom_point()ggplot(economics, aes(x = date, y = unemploy)) +geom_vline(xintercept =7.5, color ="orange", size =1) +geom_line(color ="blue", size =1) +geom_point() ggplot(economics, aes(x = date, y = unemploy)) +geom_abline(intercept =4000, slope =0.5, color ="orange", size =1) +geom_line(color ="blue", size =1) +geom_point()
Trabalhando com cores
As escalas de cores são de dois tipos principais:
As escalas discretas têm cores separadas
Melhor com variáveis do tipo fator
As escalas Contínuas formam um gradiente
Melhor com variáveis numéricas
Existem duas maneiras de controlar a cor:
Você pode mapear a cor para uma variável
Assumirá valores diferentes
Você pode definir a cor para um valor
Ele assumirá um valor apenas
Cores - Prática
# CONFIGURAÇÃO: Precisaremos do tidyverse e de um conjunto de dados de exemplolibrary(tidyverse)mpg# ==============================================================================# CASO DE USO: Escalas de cores contínuas funcionam bem com variáveis numéricasggplot(mpg, aes(x = hwy, y = cty, color = displ)) +geom_point(size =4)ggplot(mpg, aes(x = hwy, y = cty, color = displ)) +geom_point(size =4) +scale_color_continuous(type ="viridis")# ==============================================================================# CASO DE USO: Use uma escala de cores discreta com variáveis categóricasggplot(mpg, aes(x = displ, y = hwy, color = drv)) +geom_point()ggplot(mpg, aes(x = displ, y = hwy, color = drv)) +geom_point() +scale_color_discrete(name ="Drivetrain", breaks =c("4", "f", "r"), labels =c("Four Wheel", "Front Wheel", "Rear Wheel") )# ==============================================================================# ARMADILHA: Não se esqueça de definir variáveis categóricas como fatoresggplot(mpg, aes(x = displ, y = hwy, color = cyl)) +geom_point() # o R supõe que você quer uma escala contínuaggplot(mpg, aes(x = displ, y = hwy, color =factor(cyl))) +geom_point() +scale_color_discrete(name ="Cylinders")# ==============================================================================# LIÇÃO: Defina a estética de cor de um geom para que ele sempre tenha essa corggplot(mpg, aes(x = displ, y = hwy)) +geom_point(color ="red")# ==============================================================================# ARMADILHA: No entanto, faça isso dentro de geom() e não de aes()ggplot(mpg, aes(x = displ, y = hwy, color ="blue")) +geom_point() # não intencional# ==============================================================================# LIÇÃO: Se você definir e mapear a cor, vai dar bom.ggplot(mpg, aes(x = displ, y = hwy, color = drv)) +geom_point(color ="blue")
Temas
Temas controlam a aparência dos elementos não-dados
por exemplo, qual a espessura para desenhar as linhas de grade
por exemplo, onde posicionar a legenda
Temas completos alteram muitos elementos de uma só vez
Alguns estão incorporados ao ggplot2
Outros vêm em pacotes R
Elementos individuais também podem ser personalizados
# CONFIGURAÇÃO: Precisaremos do tidyverse e de um gráfico de exemplolibrary(tidyverse)p <-ggplot(mpg, aes(x = displ, y = hwy, color = drv)) +geom_point() +labs(title ="Fuel Efficiency")p# ==============================================================================# CASO DE USO: Aplicar um tema "completo"p +theme_bw()p +theme_classic()p +theme_dark()# ==============================================================================# LIÇÃO: Controle mais preciso, podemos usar theme()p +theme(legend.position ="top")p +theme(plot.title =element_text(color ="purple", face ="bold"))p +theme(panel.grid =element_blank())# OBSERVAÇÃO: Há muitos elementos para aprender, então leia a documentação!
Exportando gráficos
Podemos precisar exportar gráficos do R
por exemplo, para um artigo, pôster ou apresentação
Este trabalho está sendo executado fantasticamente pela função ggsave()
Podemos criar muitos tipos de arquivos
Podemos personalizar o tamanho exato
Eu recomendo .png para a maioria dos propósitos diários
Para publicação, prefiro .pdf ou .svg
Eles mantêm a qualidade perfeita em qualquer zoom
Exportando gráficos - Prática
# CONFIGURAÇÃO: Precisaremos do tidyverse e de um gráfico de exemplolibrary(tidyverse)p <-ggplot(mpg, aes(x = displ, y = hwy)) +geom_point() +geom_smooth() +labs(x ="Engine Displacement", y ="Highway MPG")p# ==============================================================================# CASO DE USO: Salvar um objeto ggplot específico em um arquivoggsave(filename ="pfinal.png", plot = p)# ==============================================================================# LIÇÃO: Especifique o tamanho do arquivo a ser criadoggsave(filename ="pfinal2.png", plot = p, width =6, height =3, units ="in")# ==============================================================================# LIÇÃO: Basta alterar a extensão para criar um tipo de arquivo diferenteggsave(filename ="pfinal2.pdf", plot = p, width =6, height =3, units ="in")# ==============================================================================# ARMADILHA: Criar um arquivo muito grande pode resultar em texto pequenoggsave(filename ="p_poster.png", plot = p, width =12, height =8, units ="in")# ==============================================================================# DICA: Você pode aumentar rapidamente o tamanho do texto usando base_sizep2 <- p +theme_grey(base_size =24)ggsave(filename ="p_poster2.png", plot = p2,width =12, height =8, units ="in")